package adapter

import (
	"net/http"

	"github.com/gin-gonic/gin"
	"github.com/mars/internal/admin/core/application/client"
	"github.com/mars/internal/admin/core/application/service"
	"github.com/mars/internal/admin/core/domain"
	"github.com/mars/internal/pkg/gins"
	"github.com/mars/pkg/errors"
)

type OrderController struct {
	srv       service.Service
	validator *domain.OrderValidator
}

func NewOrderController(fc domain.Factory) *OrderController {
	return &OrderController{
		srv:       service.NewService(fc),
		validator: domain.NewOrderValidator(),
	}
}

// GetOrderList 获取订单列表
// @Summary 获取订单列表
// @Description 分页查询订单信息，支持按状态、支付方式、商品类型筛选和关键字搜索
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param page query int false "页码" default(1)
// @Param size query int false "每页数量" default(20)
// @Param status query string false "订单状态" Enums(pending,paid,shipped,delivered,completed,cancelled,refunded,refunding)
// @Param paymentMethod query string false "支付方式" Enums(wechat,alipay)
// @Param isVipOrder query bool false "是否VIP订单"
// @Param productType query string false "商品类型" Enums(vip,ticket,physical)
// @Param keyword query string false "关键字搜索（订单号、用户openid、商品名称）"
// @Param startTime query string false "开始时间" format(date)
// @Param endTime query string false "结束时间" format(date)
// @Param minAmount query int false "最小金额（分）"
// @Param maxAmount query int false "最大金额（分）"
// @Param hasVipDiscount query bool false "是否有VIP折扣"
// @Param sort query string false "排序字段" default(createTime)
// @Param order query string false "排序方向" Enums(asc,desc) default(desc)
// @Success 200 {object} map[string]interface{} "{"data": [订单列表], "total": 总数}"
// @Failure 400 {object} map[string]interface{} "请求参数错误"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/list [get]
func (oc *OrderController) GetOrderList(cxt *gin.Context) (interface{}, int64, error) {
	// 使用domain层验证器验证查询参数
	params, err := oc.validator.ValidateQueryParams(cxt)
	if err != nil {
		return nil, 0, err
	}

	orders, total, err := oc.srv.OrderSrv().GetOrderList(cxt, params)
	if err != nil {
		return nil, 0, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, total, nil
}

// GetOrder 根据ID获取订单详情
// @Summary 获取订单详情
// @Description 根据订单ID查询订单详细信息
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param id path string true "订单ID"
// @Success 200 {object} client.OrderView "订单详细信息"
// @Failure 400 {object} map[string]interface{} "订单ID参数缺失"
// @Failure 404 {object} map[string]interface{} "订单不存在"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/detail/{id} [get]
func (oc *OrderController) GetOrder(cxt *gin.Context) (interface{}, error) {
	// 使用domain层验证器验证订单ID
	orderID, err := oc.validator.ValidateOrderID(cxt, "id")
	if err != nil {
		return nil, err
	}

	order, err := oc.srv.OrderSrv().GetOrder(cxt, orderID)
	if err != nil {
		return nil, err
	}

	orderView := client.ToOrderView(order)
	return orderView, nil
}

// UpdateOrderStatus 更新订单状态
// @Summary 更新订单状态
// @Description 管理员更新订单状态（发货、完成、退款等）
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param id path string true "订单ID"
// @Param status body object true "{"status": "shipped|delivered|completed|refunded|refunding"}"
// @Success 200 {object} map[string]interface{} "{"message": "Order status updated successfully"}"
// @Failure 400 {object} map[string]interface{} "请求参数错误"
// @Failure 401 {object} map[string]interface{} "未授权"
// @Failure 403 {object} map[string]interface{} "权限不足"
// @Failure 404 {object} map[string]interface{} "订单不存在"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/status/{id}/{status} [put]
func (oc *OrderController) UpdateOrderStatus(cxt *gin.Context) (*gins.Response, error) {
	// 使用domain层验证器验证订单ID
	orderID, err := oc.validator.ValidateOrderID(cxt, "id")
	if err != nil {
		return nil, err
	}
	status, err := oc.validator.ValidateOrderStatus(cxt, "status")
	if err != nil {
		return nil, err
	}

	err = oc.srv.OrderSrv().UpdateOrderStatus(cxt, orderID, status)
	if err != nil {
		return nil, err
	}

	return gins.NewSuccessResponse("Order status updated successfully"), nil
}

// ProcessRefund 处理订单退款
// @Summary 处理订单退款
// @Description 管理员处理订单退款申请
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param id path string true "订单ID"
// @Param refund body object true "{"reason": "退款原因", "amount": 退款金额(可选,分)}"
// @Success 200 {object} map[string]interface{} "{"message": "Refund processed successfully"}"
// @Failure 400 {object} map[string]interface{} "请求参数错误"
// @Failure 401 {object} map[string]interface{} "未授权"
// @Failure 403 {object} map[string]interface{} "权限不足"
// @Failure 404 {object} map[string]interface{} "订单不存在"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/refund/{id} [post]
func (oc *OrderController) ProcessRefund(cxt *gin.Context) (*gins.Response, error) {
	// 使用domain层验证器验证订单ID
	orderID, err := oc.validator.ValidateOrderID(cxt, "id")
	if err != nil {
		return nil, err
	}

	var req struct {
		Reason string `json:"reason" binding:"required"`
		Amount *int   `json:"amount,omitempty"` // 可选，不填则全额退款
	}
	if err := cxt.ShouldBindJSON(&req); err != nil {
		return nil, errors.New(http.StatusBadRequest, "invalid JSON format: "+err.Error())
	}

	// 使用domain层验证器验证退款请求
	if err := oc.validator.ValidateRefundRequest(req.Reason, req.Amount); err != nil {
		return nil, err
	}

	err = oc.srv.OrderSrv().ProcessRefund(cxt, orderID, req.Reason, req.Amount)
	if err != nil {
		return nil, err
	}

	return gins.NewSuccessResponse("Refund processed successfully"), nil
}

// GetOrderStats 获取订单统计信息
// @Summary 获取订单统计信息
// @Description 获取订单数量、金额等多维度统计信息
// @Tags 订单管理
// @Accept json
// @Produce json
// @Success 200 {object} client.OrderStatsView "统计信息"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/stats [get]
func (oc *OrderController) GetOrderStats(cxt *gin.Context) (interface{}, error) {
	stats, err := oc.srv.OrderSrv().GetOrderStats(cxt)
	if err != nil {
		return nil, err
	}

	statsView := client.ToOrderStatsView(stats)
	return statsView, nil
}

// SearchOrders 搜索订单
// @Summary 搜索订单
// @Description 根据关键字搜索订单（订单号、用户openid、商品名称）
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param keyword query string true "搜索关键字"
// @Success 200 {array} client.OrderView "订单列表"
// @Failure 400 {object} map[string]interface{} "请求参数错误"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/search [get]
func (oc *OrderController) SearchOrders(cxt *gin.Context) (interface{}, error) {
	// 使用domain层验证器验证搜索关键字
	keyword, err := oc.validator.ValidateSearchKeyword(cxt)
	if err != nil {
		return nil, err
	}

	orders, err := oc.srv.OrderSrv().SearchOrders(cxt, keyword)
	if err != nil {
		return nil, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, nil
}

// GetOrdersByStatus 根据状态获取订单列表
// @Summary 根据状态查询订单
// @Description 根据订单状态查询订单列表
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param status path string true "订单状态" Enums(pending,paid,shipped,delivered,completed,cancelled,refunded,refunding)
// @Success 200 {array} client.OrderView "订单列表"
// @Failure 400 {object} map[string]interface{} "状态参数错误或无效"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/status/{status} [get]
func (oc *OrderController) GetOrdersByStatus(cxt *gin.Context) (interface{}, error) {
	// 使用domain层验证器验证订单状态
	status, err := oc.validator.ValidateOrderStatus(cxt, "status")
	if err != nil {
		return nil, err
	}

	orders, err := oc.srv.OrderSrv().GetOrdersByStatus(cxt, status)
	if err != nil {
		return nil, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, nil
}

// GetOrdersByPaymentMethod 根据支付方式获取订单列表
// @Summary 根据支付方式查询订单
// @Description 根据支付方式查询订单列表
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param method path string true "支付方式" Enums(wechat,alipay)
// @Success 200 {array} client.OrderView "订单列表"
// @Failure 400 {object} map[string]interface{} "支付方式参数错误或无效"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/payment/{method} [get]
func (oc *OrderController) GetOrdersByPaymentMethod(cxt *gin.Context) (interface{}, error) {
	method := cxt.Param("method")
	if method == "" {
		return nil, errors.New(http.StatusBadRequest, "payment method is required")
	}

	// 验证支付方式
	if err := oc.validator.ValidatePaymentMethod(method); err != nil {
		return nil, err
	}

	orders, err := oc.srv.OrderSrv().GetOrdersByPaymentMethod(cxt, domain.PaymentMethod(method))
	if err != nil {
		return nil, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, nil
}

// GetVipOrders 获取VIP订单列表
// @Summary 获取VIP订单列表
// @Description 查询所有VIP用户的订单
// @Tags 订单管理
// @Accept json
// @Produce json
// @Success 200 {array} client.OrderView "VIP订单列表"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/vip [get]
func (oc *OrderController) GetVipOrders(cxt *gin.Context) (interface{}, error) {
	orders, err := oc.srv.OrderSrv().GetVipOrders(cxt)
	if err != nil {
		return nil, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, nil
}

// ExportOrders 导出订单数据
// @Summary 导出订单数据
// @Description 根据筛选条件导出订单数据，支持Excel格式
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param status query string false "订单状态" Enums(pending,paid,shipped,delivered,completed,cancelled,refunded,refunding)
// @Param paymentMethod query string false "支付方式" Enums(wechat,alipay)
// @Param isVipOrder query bool false "是否VIP订单"
// @Param productType query string false "商品类型" Enums(vip,ticket,physical)
// @Param keyword query string false "关键字搜索"
// @Param startTime query string false "开始时间" format(date)
// @Param endTime query string false "结束时间" format(date)
// @Param minAmount query int false "最小金额（分）"
// @Param maxAmount query int false "最大金额（分）"
// @Param hasVipDiscount query bool false "是否有VIP折扣"
// @Success 200 {array} client.OrderView "订单数据"
// @Failure 400 {object} map[string]interface{} "请求参数错误"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/export [get]
func (oc *OrderController) ExportOrders(cxt *gin.Context) (interface{}, error) {
	// 使用domain层验证器验证查询参数（用于导出筛选）
	params, err := oc.validator.ValidateQueryParams(cxt)
	if err != nil {
		return nil, err
	}

	orders, err := oc.srv.OrderSrv().ExportOrders(cxt, params)
	if err != nil {
		return nil, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, nil
}

// GetOrdersByProductType 根据商品类型获取订单列表
// @Summary 根据商品类型查询订单
// @Description 根据商品类型查询包含该类型商品的订单列表
// @Tags 订单管理
// @Accept json
// @Produce json
// @Param type path string true "商品类型" Enums(vip,ticket,physical)
// @Success 200 {array} client.OrderView "订单列表"
// @Failure 400 {object} map[string]interface{} "商品类型参数错误或无效"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/type/{type} [get]
func (oc *OrderController) GetOrdersByProductType(cxt *gin.Context) (interface{}, error) {
	productTypeStr := cxt.Param("type")
	if productTypeStr == "" {
		return nil, errors.New(http.StatusBadRequest, "product type is required")
	}

	// 验证商品类型
	productType, err := oc.validator.ValidateProductTypeValue(productTypeStr)
	if err != nil {
		return nil, err
	}

	// 构建查询参数
	params := domain.OrderQueryParams{
		PaginationParams: domain.DefaultPaginationParams,
		ProductType:      productType,
	}

	orders, _, err := oc.srv.OrderSrv().GetOrderList(cxt, params)
	if err != nil {
		return nil, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, nil
}

// GetOrdersWithDiscounts 获取有折扣的订单列表
// @Summary 获取有折扣的订单列表
// @Description 查询所有包含VIP折扣的订单
// @Tags 订单管理
// @Accept json
// @Produce json
// @Success 200 {array} client.OrderView "有折扣的订单列表"
// @Failure 500 {object} map[string]interface{} "服务器内部错误"
// @Router /api/v1/admin/order/discounts [get]
func (oc *OrderController) GetOrdersWithDiscounts(cxt *gin.Context) (interface{}, error) {
	hasVipDiscount := true
	params := domain.OrderQueryParams{
		PaginationParams: domain.DefaultPaginationParams,
		HasVipDiscount:   &hasVipDiscount,
	}

	orders, _, err := oc.srv.OrderSrv().GetOrderList(cxt, params)
	if err != nil {
		return nil, err
	}

	// 转换为view层结构体
	orderViews := client.ToOrderViewList(orders)
	return orderViews, nil
}
